#include <stdlib.h>
#include <string.h>
#include <directfb.h>

#include "dtk_types.h"
#include "dtk_debug.h"
#include "dtk_actor.h"
#include "dtk_rectangle.h"

const DString DTK_TYPE_RECTANGLE = "DTKRectangle";


static void rectangle_draw (DTKActor* self, DTKGC* gc, DRegion* region)
{
    DTKRectangle* rectangle = (DTKRectangle*) self;
    DInt line_width;

    DTK_TYPE_ASSERT (self, DTK_TYPE_RECTANGLE);

    dtk_region_dump (__func__, region);

    gc->surface->SetColor (gc->surface,
                    rectangle->color.red,
                    rectangle->color.green,
                    rectangle->color.blue,
                    rectangle->color.alpha);

    line_width = rectangle->line_width;

    if (line_width > dtk_region_width(region) / 2
        || line_width > dtk_region_height(region) / 2)
    {
        
        gc->surface->FillRectangle (gc->surface,
            region->x1,
            region->y1,
            dtk_region_width(region) - 1,
            dtk_region_height(region) - 1);
    }
    else if (line_width <= 0)
    {
        gc->surface->DrawRectangle (gc->surface,
            region->x1,
            region->y1,
            dtk_region_width(region) - 1,
            dtk_region_height(region) - 1);
    }
    else
    {
        DFBRectangle rect[4];

        rect[0].x = region->x1;
        rect[0].y = region->y1;
        rect[0].w = rectangle->line_width;
        rect[0].h = dtk_region_height(region) - 1;

        rect[2] = rect[0];
        rect[2].x = region->x1 + 
            dtk_region_width(region)
            - rectangle->line_width;

        rect[1] = rect[0];
        rect[1].w = dtk_region_width(region) - 1;
        rect[1].h = rectangle->line_width;

        rect[3] = rect[1];
        rect[3].y = region->y1 + 
            dtk_region_height(region)
            - rectangle->line_width;
        
        gc->surface->FillRectangles (gc->surface, rect, 4);

    }

    return;
}

DTKActor* dtk_rectangle_new(void)
{
    DTKActor*       actor;
    DTKRectangle*   rectangle;
    DTKActorCallback*       funcs;
    DColor                color = {0x00, 0x00, 0x00, 0xff};

    actor = dtk_actor_init (sizeof(DTKRectangle), DTK_TYPE_RECTANGLE,
        DACAPS_NONE, NULL);
    rectangle = (DTKRectangle*)rectangle;

    dtk_rectangle_set_color (actor, &color);
    
    funcs = DTK_ACTOR_CALLBACK(actor);

    funcs->draw = rectangle_draw;


    return actor;
}

void dtk_rectangle_set_color (DTKActor* self, DColor* color)
{
    DTKRectangle* rectangle = (DTKRectangle*) self;

    DTK_TYPE_ASSERT (self, DTK_TYPE_RECTANGLE);

    rectangle->color = *color;
    return;
}

void dtk_rectangle_get_color (DTKActor* self, DColor* color)
{
    DTKRectangle* rectangle = (DTKRectangle*) self;

    DTK_TYPE_ASSERT (self, DTK_TYPE_RECTANGLE);

    *color = rectangle->color;
    return;
}

void dtk_rectangle_set_line_width(DTKActor * self, DInt line_width)
{
    DTKRectangle* rectangle = (DTKRectangle*) self;

    DTK_TYPE_ASSERT (self, DTK_TYPE_RECTANGLE);

    if (line_width < 0)
    {
        return;
    }    

    rectangle->line_width = line_width;
    return;
}

DInt dtk_rectangle_get_line_width(DTKActor * self)
{
    DTKRectangle* rectangle = (DTKRectangle*) self;

    DTK_TYPE_ASSERT (self, DTK_TYPE_RECTANGLE);

    return rectangle->line_width;
}
